{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 类\n",
    "\n",
    "\n",
    "    class Person:\n",
    "        def __init__(self, name):   # 定义self和静态属性\n",
    "            self.name = name\n",
    "\n",
    "        def get_name(self):         # 参数self用来表明该方法是该实例的动态属性\n",
    "            return self.name\n",
    "\n",
    "        def get_age(self, color):\n",
    "            d = {}\n",
    "            d[self.name] = color\n",
    "        return d\n",
    "\n",
    "Python中就规定好了，函数的第一个参数，就必须是实例对象本身，并且建议，约定俗成，把其名字写为self，`实例`相对`其他`而言就是`自身`\n",
    "\n",
    "`self.name = name`：建立实例的一个属性，这个属性的名字也是`name`，这个属性的值等于参数`name`所传入的值。\n",
    "> 这里的属性`self.name`和参数`name`是纯属巧合，也可以设置成`self.xxx = name`\n",
    "\n",
    "### 实例\n",
    "\n",
    "类是对象的定义，实例才是真实的物件。比如“人”是一个类，但是“人”终究不是具体的某个活体，只有“张三”、“李四”才是具体的物件，但他们具有“人”所定义的属性和方法。“张三”、“李四”就是“人”的实例。\n",
    "\n",
    "    if __name__ == \"__main__\":\n",
    "        girl = Person(\"canglaoshi\")\n",
    "        print(girl.name)\n",
    "        name = girl.get_name()\n",
    "        print(name)\n",
    "        her_color = girl.color(\"white\")\n",
    "        print(her_color)\n",
    "\n",
    "`girl = Person('canglaoshi')`是利用上面的类创建实例。\n",
    "\n",
    "创建实例，调用类`Person()`，首先就执行初始化函数，初始化函数有两个参数`self`和`name`，其中`self`是默认参数，不需要传值；`name`则需要给它传值，所以用`Person('canglaoshi')`的样式，就是为初始化函数中的`name`参数传值了，即`name = 'canglaoshi'`。\n",
    "\n",
    "`girl`就是一个实例，它有属性和方法。\n",
    "\n",
    "先说属性。实例化过程中，首先要执行`__init__()`，并通过参数`name`，使得实例属性`self.name = 'canglaoshi'`。这里先稍微提一下`self`的作用，它实质上就是实例对象本身，当你用实例调用方法的时候，由解释器将那个实例传递给方法，所以不需要显示地为这个参数传值。那么`self.name`也顺理成章地是实例的属性了。所以`print(girl.name)`的结果应该是`canglaoshi`。\n",
    "\n",
    "这就是初始化的功能。简而言之，通过初始化函数，确定了这个实例的“基本属性”（实例是什么样子的）。\n",
    "\n",
    "`girl.get_name()`是通过实例来调用方法，也可以说建立了实例`girl`，这个实例就具有了`get_name()`方法。虽然在类里面，该方法的第一个参数是`self`，跟前面所述原因一样，通过实例调用该方法——实例方法——的时候，不需要显示地为`self`传递值，所以，在这里就不需要写任何参数。观察类中这个方法的代码可知，它的功能就是返回实例属性`self.name`的值，所以`print name`或者`print(name)`的结果是`canglaoshi`。\n",
    "\n",
    "`girl.color(\"white\")`之所以要给参数传值，是因为`def color(self, color)`中有参数`color`。另外，这个方法里面也使用了`self.name`实例属性。最终该方法返回的是一个字典。所以`print her_color`或者`print(her_color)`的结果是`{'canglaoshi': 'white'}`。\n",
    "\n",
    "刚才以`girl = Person(\"canglaoshi\")`的方式，建立了一个实例，仿照它，还可以建立更多的实例，比如`boy = Person(\"zhangsan\")`等等。也就是一个类，可以建立多个实例。所以“类提供默认行为，是实例的工厂”（源自Learning Python），这句话道破了类和实例的关系。所谓工厂，就是可以用同一个模子做出很多具体的产品。类就是那个模子，实例就是具体的产品。\n",
    "\n",
    "这就是通过类建立实例，并且通过实例来调用其属性和方法的过程。\n"
   ]
  }
 ],
 "metadata": {
  "hide_input": false,
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.5.4rc1"
  },
  "toc": {
   "nav_menu": {},
   "number_sections": false,
   "sideBar": true,
   "skip_h1_title": false,
   "toc_cell": false,
   "toc_position": {},
   "toc_section_display": "block",
   "toc_window_display": true
  },
  "varInspector": {
   "cols": {
    "lenName": "15",
    "lenType": "10",
    "lenVar": "60"
   },
   "kernels_config": {
    "python": {
     "delete_cmd_postfix": "",
     "delete_cmd_prefix": "del ",
     "library": "var_list.py",
     "varRefreshCmd": "print(var_dic_list())"
    },
    "r": {
     "delete_cmd_postfix": ") ",
     "delete_cmd_prefix": "rm(",
     "library": "var_list.r",
     "varRefreshCmd": "cat(var_dic_list()) "
    }
   },
   "types_to_exclude": [
    "module",
    "function",
    "builtin_function_or_method",
    "instance",
    "_Feature"
   ],
   "window_display": false
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
